package me.hekr.iotos.api.service;


import java.util.List;
import java.util.Map;
import me.hekr.iotos.api.dto.BatchAddDeviceResp;
import me.hekr.iotos.api.dto.CloudSendMsgDTO;
import me.hekr.iotos.api.dto.DelTopoResp;
import me.hekr.iotos.api.dto.DevIdListReq;
import me.hekr.iotos.api.dto.Device;
import me.hekr.iotos.api.dto.DeviceAddReq;
import me.hekr.iotos.api.dto.DeviceApiDTO;
import me.hekr.iotos.api.dto.DeviceDTO;
import me.hekr.iotos.api.dto.DevicePacketResp;
import me.hekr.iotos.api.dto.DeviceUpdateNameReq;
import me.hekr.iotos.api.dto.LoginRsp;
import me.hekr.iotos.api.dto.ModelProtocolDTO;
import me.hekr.iotos.api.dto.Product;
import me.hekr.iotos.api.dto.Snapshot;
import me.hekr.iotos.api.dto.klink.AddTopoResp;
import me.hekr.iotos.api.dto.klink.KlinkResp;
import me.hekr.iotos.api.dto.klink.ModelData;
import me.hekr.iotos.api.dto.klink.TopoSub;
import me.hekr.iotos.api.enums.DeviceType;
import me.hekr.iotos.api.util.Pagec;
import org.omg.CORBA.Any;
import org.slf4j.Logger;
import org.slf4j.LoggerFactory;
import retrofit2.Call;
import retrofit2.http.Body;
import retrofit2.http.DELETE;
import retrofit2.http.GET;
import retrofit2.http.POST;
import retrofit2.http.PUT;
import retrofit2.http.Path;
import retrofit2.http.Query;
import retrofit2.http.QueryMap;

public interface RetrofitIotService {
  Logger log = LoggerFactory.getLogger(RetrofitIotService.class);

  /**
   * 获取产品列表
   *
   * <p><a href="http://hy.hekr.me/iot-docs-test/web/content/应用开发指南/获取产品列表.html">获取产品列表</a>
   *
   * @param page 当前页，从0开始
   * @param size 分页大小，最大100，最小1
   * @return
   */
  @GET("/product")
  Call<Pagec<Product>> getProduct(@Query("page") int page, @Query("size") int size);

  /**
   * 获取物模型
   *
   * <p><a href="http://hy.hekr.me/iot-docs-test/web/content/应用开发指南/产品物模型查询.html>产品物模型查询/a>
   *
   * @param pk 产品PK
   * @return
   */
  @GET("/model/protocol/{pk}")
  Call<ModelProtocolDTO> getProtocol(@Path("pk") String pk);



  /**
   * 新增设备
   *
   * <p><a href="http://hy.hekr.me/iot-docs-test/web/content/应用开发指南/新增设备.html>新增设备</a>
   *
   * @param addReq
   * @return
   */
  @POST("/api/device/addDevice")
  Call<Device> createDevice(@Body DeviceAddReq addReq);

  /**
   * 导入设备
   *
   * <p><a href="http://hy.hekr.me/iot-docs-test/web/content/应用开发指南/导入设备.html">导入设备</a>
   *
   * @return
   */
  @PUT("/api/device/batchAddDevices")
  Call<BatchAddDeviceResp> addTopo(@Body DevIdListReq req);

  /**
   * 获取批次下所有设备
   *
   * <p><a href="http://hy.hekr.me/iot-docs-test/web/content/应用开发指南/获取批次下所有设备.html">获取批次下所有设备</a>
   *
   * @param pk 产品PK
   * @param batchName 批次名称
   * @return
   */
  @GET("/api/device/getBatchDevices/{pk}/{batchName}")
  Call<List<Device>> getBatchDevices(@Path("pk") String pk, @Path("batchName") String batchName);

  /**
   * 查询设备列表
   *
   * <p><a href="http://hy.hekr.me/iot-docs-test/web/content/应用开发指南/查询设备列表.html">查询设备列表</a>
   *
   * @param params
   * @return
   */
  @GET("/api/device/getDeviceList")
  Call<Pagec<Device>> getDeviceList(@QueryMap Map<String, Object> params);

  /**
   * 更改设备名称
   *
   * <p><a href="http://hy.hekr.me/iot-docs-test/web/content/应用开发指南/更新设备.html">更改设备名称</a>
   *
   * @param req 设备信息（pk，devId，name）
   * @return
   */
  @PUT("/api/device/updateName")
  Call<Any> updateName(@Body DeviceUpdateNameReq req);

  /**
   * 查询设备详情
   *
   * <p><a href="http://hy.hekr.me/iot-docs-test/web/content/应用开发指南/查询设备详情.html">查询设备详情</a>
   *
   * @param pk 产品PK
   * @param devId 设备ID
   * @return
   */
  @GET("/api/device/deviceInfo/{pk}/{devId}")
  Call<Device> getDevice(@Path("pk") String pk, @Path("devId") String devId);

  /**
   * 批量查询状态
   *
   * <p><a href="http://hy.hekr.me/iot-docs-test/web/content/应用开发指南/批量查询状态.html">批量查询状态</a>
   *
   * @param req 设备信息（pk，devId，name）
   * @return
   */
  @POST("/api/device/getDeviceStatus")
  Call<Device> getDeviceStatus(@Body DevIdListReq req);

  /**
   * 删除设备
   *
   * <p><a href="http://hy.hekr.me/iot-docs-test/web/content/应用开发指南/删除设备.html">删除设备</a>
   *
   * @param pk 产品PK
   * @param devId 设备ID
   * @return
   */
  @DELETE("/api/device/delDevice/{pk}/{devId}")
  Call<Device> delDevice(@Path("pk") String pk, @Path("devId") String devId);

  /**
   * 获取鉴权信息
   *
   * <p><a href="http://hy.hekr.me/iot-docs-test/web/content/应用开发指南/获取Token.html">获取鉴权信息</a>
   *
   * @return
   */
  @GET("/api/user/getLoginToken")
  Call<LoginRsp> getLoginToken();

//  /**
//   * 查询历史上下行数据
//   *
//   * <p><a href="http://hy.hekr.me/iot-docs-test/web/content/应用开发指南/查询历史上下行数据.html">查询历史上下行数据"></a>
//   *
//   * @param pk 产品PK
//   * @param devId 设备ID
//   * @return
//   */
//  @GET("/api/device/getDeviceHistoryData/{pk}/{devId}")
//  Call<DevicePacketResp> getDeviceHistoryData(@Path("pk") String pk, @Path("devId") String devId);

  //  /**
  //   * 查询设备影子
  //   *
  //   * <a href="http://hy.hekr.me/iot-docs-test/web/content/应用开发指南/查询设备影子.html">查询设备影子</a>
  //   *
  //   * @return
  //   */
  //  @GET("/api/device/getSnapshot")
  //  Call<Snapshot> getSnapshot(@Query("pk") String pk, @Query("devId") String devId);

  // ===================================================
  // ====================================================

  /**
   * 新增设备
   *
   * <p><a href="http://hy.hekr.me/iot-docs-test/web/content/应用开发指南/新增设备.html">新增设备</a>
   *
   * @param reqDto 设备信息（pk，devId，name）
   * @return
   */
  @POST("/api/device/addDevice")
  Call<DeviceApiDTO> addDevice(@Body DeviceAddReq reqDto);

  /**
   * 导入设备
   *
   * <p><a href="http://hy.hekr.me/iot-docs-test/web/content/应用开发指南/导入设备.html">导入设备</a>
   *
   * @param devIdListReq （产品PK和设备ID列表）
   * @return
   */
  @POST("/api/device/batchAddDevices")
  Call<Map<String, Object>> batchAddDevices(@Body DevIdListReq devIdListReq);

  /**
   * 查询设备列表
   *
   * <p><a href="http://hy.hekr.me/iot-docs-test/web/content/应用开发指南/查询设备列表.html">查询设备列表</a>
   *
   * @param pk 产品PK
   * @param keyword 搜索关键词
   * @param page 当前页面，最大100，最小1
   * @param deviceType 节点类型（普通设备：GENERAL；中继设备：SWITCH；网关设备：GATEWAY；终端子设备：TERMINAL）
   * @param online 是否在线，true为在线
   * @param size 分页大小，默认10，
   * @return
   */
  @GET("/api/device/getDeviceList")
  Call<Pagec<DeviceApiDTO>> getDeviceList(
      @Query("pk") String pk,
      @Query("keyword") String keyword,
      @Query("page") int page,
      @Query("deviceType") DeviceType deviceType,
      @Query("online") Boolean online,
      @Query("size") int size);

  //  /**
  //   * 更改设备名称
  //   *
  //   * <a href="http://hy.hekr.me/iot-docs-test/web/content/应用开发指南/更新设备.html">更改设备名称</a>
  //   *
  //   * @param reqDto
  //   */
  //  @PUT("/api/device/updateName")
  //   void updateName(@Query("reqDto") DeviceAddReq reqDto);

  /**
   * ????
   *
   * <p><a href="http://hy.hekr.me/iot-docs-test/web/content/应用开发指南/???.html">????</a>
   *
   * @param reqDto
   */
  @PUT("/api/device/updateTags")
  Call<Any> updateTags(@Body DeviceAddReq reqDto);

  /**
   * 查询设备详情
   *
   * <p><a href="http://hy.hekr.me/iot-docs-test/web/content/应用开发指南/查询设备详情.html">查询设备详情</a>
   *
   * @param pk 产品PK
   * @param devId 设备ID
   * @return
   */
  @GET("/api/device/deviceInfo/{pk}/{devId}")
  Call<DeviceApiDTO> deviceInfo(@Path("pk") String pk, @Path("devId") String devId);

  /**
   * 查询设备影子
   *
   * <p><a href="http://hy.hekr.me/iot-docs-test/web/content/应用开发指南/查询设备影子.html">查询设备影子</a>
   *
   * @param pk 产品PK
   * @param devId 设备ID
   * @return
   */
  @GET("/api/device/getSnapshot")
  Call<Snapshot> getDeviceSnapshot(@Query("pk") String pk, @Query("devId") String devId);

  /**
   * 删除设备
   *
   * <p><a href="http://hy.hekr.me/iot-docs-test/web/content/应用开发指南/删除设备.html">删除设备</a>
   *
   * @param pk 产品PK
   * @param devId 设备ID
   * @param delSnapshot
   */
  @DELETE("/api/device/delDevice/{pk}/{devId}")
  Call<Any> delDevice(
      @Path("pk") String pk,
      @Path("devId") String devId,
      @Query("delSnapshot") boolean delSnapshot);

  /**
   * 批量查删除设备
   *
   * <p><a href="http://hy.hekr.me/iot-docs-test/web/content/应用开发指南/？？？.html">批量删除设备</a>
   *
   * @param deviceList 设备DTO列表
   */
  @DELETE("/api/device/batchDelDevice")
  Call<Any> bathDelDevice(@Query("deviceList") List<DeviceDTO> deviceList);

  /**
   * 查询历史上下行数
   *
   * <p><a href="http://hy.hekr.me/iot-docs-test/web/content/应用开发指南/查询历史上下行数.html">查询历史上下行数</a>
   *
   * @param pk 产品PK
   * @param devId 设备ID
   * @param startTime 开始事件
   * @param endTime 结束事件
   * @param action 事件
   * @param page 当前页 从0开始
   * @param size 分页大小，最大100，最小1
   * @return
   */
  @GET("/api/device/getDeviceHistoryData/{pk}/{devId}")
  Call<List<DevicePacketResp>> getDeviceHistoryData(
      @Path("pk") String pk,
      @Path("devId") String devId,
      @Query("startTime") Long startTime,
      @Query("endTime") Long endTime,
      @Query("action") String action,
      @Query("page") int page,
      @Query("size") int size);

  /**
   * 下发控制命令
   *
   * <p><a href="http://hy.hekr.me/iot-docs-test/web/content/应用开发指南/下发控制命令.html">下发控制命令</a>
   *
   * @param pk 产品PK
   * @param devId 设备ID
   * @param data （cmd 命令标识符 ，params 参数值）
   * @return
   */
  @POST("/api/device/cloudSend/{pk}/{devId}")
  Call<KlinkResp> deviceCloudSend(
      @Path("pk") String pk, @Path("devId") String devId, @Query("data") ModelData data);

  /**
   * 查询命令状态
   *
   * <p><a href="http://hy.hekr.me/iot-docs-test/web/content/应用开发指南/查询命令状态.html">查询命令状态</a>
   *
   * @param messageId 所查询命令的ID
   * @return
   */
  @GET("/api/device/cloudSendMsgInfo/{messageId}")
  Call<CloudSendMsgDTO> cloudSendMsgInfo(@Path("messageId") String messageId);

  /**
   * 查询历史控制命令
   *
   * <p><a href="http://hy.hekr.me/iot-docs-test/web/content/应用开发指南/查询历史控制命令.html">查询历史控制命令</a>
   *
   * @param page 当前页面，最小0
   * @param size 分页大小，最大100，最小0
   * @param pk 产品PK
   * @param devId 设备ID
   * @param startTime 查询开始时间
   * @param endTime 查询结束事件
   * @return
   */
  @GET("/api/device/cloudSendMsgList")
  Call<Pagec<CloudSendMsgDTO>> cloudSendMsgList(
      @Query("page") Integer page,
      @Query("size") Integer size,
      @Query("pk") String pk,
      @Query("devId") String devId,
      @Query("startTime") Long startTime,
      @Query("endTime") Long endTime);

  /**
   * 网关添加子设备
   *
   * <p><a href="http://hy.hekr.me/iot-docs-test/web/content/应用开发指南/网关添加子设备.html">网关添加子设备</a>
   *
   * @param pk 产品PK
   * @param devId 设备ID
   * @param sub
   * @return
   */
  @PUT("/api/device/addTopo/{pk}/{devId}")
  Call<AddTopoResp> addTopo(@Path("pk") String pk, @Path("devId") String devId, @Body TopoSub sub);

  /**
   * 网关删除子设备
   *
   * <p><a href="http://hy.hekr.me/iot-docs-test/web/content/应用开发指南/???.html">网关删除子设备</a>
   *
   * @param pk 产品PK
   * @param devId 设备ID
   * @param sub
   * @return
   */
  @PUT("/api/device/delTopo/{pk}/{devId}")
  Call<DelTopoResp> delTopo(@Path("pk") String pk, @Path("devId") String devId, @Body TopoSub sub);
}
